
package com.studiofortress.sf.util;

import java.lang.reflect.Array;

/**
 * This is a fully static class offering some common utility functions for
 * working with arrays. Some of these functions are built for Java 5
 * compatibility.
 *
 * @author Joseph Lenton - JosephLenton@StudioFortress.com
 */
public final class ArrayUtil
{
    /**
     * No Construstor.
     */
    private ArrayUtil() { }

    public static <A> A[] copyOf(final A[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static <A> A[] copyOf(final A[] arr, int newSize)
    {
        return (A[]) copyOf(arr, newSize, arr.getClass());
    }

    private static <T,U> T[] copyOf(U[] arr, int newSize, Class<? extends T[]> newType) {
        T[] copy = ((Object)newType == (Object)Object[].class)
            ? (T[]) new Object[newSize]
            : (T[]) Array.newInstance(newType.getComponentType(), newSize);
        System.arraycopy(arr, 0, copy, 0, Math.min(arr.length, newSize));
        return copy;
    }

    public static int[] copyOf(final int[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static int[] copyOf(final int[] arr, int newSize)
    {
        final int[] tempArr = new int[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static double[] copyOf(final double[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static double[] copyOf(final double[] arr, int newSize)
    {
        final double[] tempArr = new double[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static float[] copyOf(final float[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static float[] copyOf(final float[] arr, int newSize)
    {
        final float[] tempArr = new float[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static byte[] copyOf(final byte[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static byte[] copyOf(final byte[] arr, int newSize)
    {
        final byte[] tempArr = new byte[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static char[] copyOf(final char[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static char[] copyOf(final char[] arr, int newSize)
    {
        final char[] tempArr = new char[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static long[] copyOf(final long[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static long[] copyOf(final long[] arr, int newSize)
    {
        final long[] tempArr = new long[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }

    public static boolean[] copyOf(final boolean[] arr)
    {
        return copyOf(arr, arr.length);
    }

    public static boolean[] copyOf(final boolean[] arr, int newSize)
    {
        final boolean[] tempArr = new boolean[newSize];
        System.arraycopy(arr, 0, tempArr, 0, Math.min(arr.length, newSize));
        return tempArr;
    }
}
